✅@2022-07-27 山と渓谷を全部Gyazoにuploadする
目的
Gyazoの検索から探せるようにする
やること
すでにuploadしてある号は飛ばす
いいや。重複してても気にせずuploadしてしまおう
重複して何か不便があるわけでもないし
それに本当に画像データが全く同じなら、uploadしても何も起きないはずだし
metadataの更新すらされないのはちょっと困るかもだけど
2014年1月号までuploadしてあるみたい
それ以外をuploadする
2022-07-27
19:46:54 まとめてuploadするdeno scriptを新しく作った
手作業の手間が多い
全ての雑誌を一括してuploadするDeno scriptを組んだほうがいいな。時間の無駄だ。
18:27:58 2015-12までuploadした
09:17:09 2014-12までuploadした
前処理
使ったscriptの都合上、一部乱丁がある
乱丁を直した号から順にuploadしたい
2022-07-27 18:29:04 めんどくさくてやっていない
どうuploadするか
referrerはなしでいいや
ページタイトル
雑誌の名前とページ数だけ載せておこう
特集名まで書くのは大変なのでやらない
uploaderの実装
DenoでCLIを作る
スピナーとupload状況を表示したいな
upload errorが出たら、それも表示する
2022-07-26 18:57:44 おかしい。半分しかuploadされない
created_atが全く同じだと、uploadに成功してもserver側で保存されないみたい?
createdの指定をやめよう
19:20:37 直ったっぽい!
code:ts
import { uploadBulk } from "../複数の画像ファイルをGyazoにuploadするscript/upload.ts";
import { useStatusBar } from "../scrapbox-userscript-std/dom.ts";
import { upload } from "../scrapbox-file-uploader/mod.ts";
const main = async () => {
const URLs = [] as string[];
const { render, dispose } = useStatusBar();
const errorBar = useStatusBar();
const infoBar = useStatusBar();
try {
const fileList = await upload({ accept: "*.jpeg, *.png", multiple: true });
if (!fileList) return;
const files = Array.from(fileList)
.sort((a, b) => parseInt(a.name) - parseInt(b.name));
let counter = 0;
const errors = [] as number[];
for await (const result of uploadBulk(
files,
{
title: "『山と渓谷 2014年5月号』",
noIndex: true,
},
)) {
counter++;
if (!result.success) {
if (!(result.reason instanceof Error)) throw result.reason;
console.error(result.reason);
errors.push(counter);
errorBar.render(
{ type: "exclamation-triangle" },
{
type: "text",
text: ${result.reason.name} ${result.reason.message},
},
);
continue;
} else {
const { permalink_url, name, index } = result.value;
URLsindex = permalink_url; infoBar.render(
{ type: "text", text: ${name} ${permalink_url} },
);
}
render(
{ type: "spinner" },
{
type: "text",
text: `${files.length} images, ${
counter - errors.length
} uploaded, ${errors.length} failed`,
},
);
}
render(
{ type: "check-circle" },
{ type: "text", text: Finish uploading. },
);
console.log(URLs);
console.log(errors);
window.open(URL.createObjectURL(blob));
} finally {
setTimeout(() => {
errorBar.dispose();
infoBar.dispose();
dispose();
}, 1000);
}
};
await main();
directory中のすべてのzipファイルから画像を全部Gyazoにuploadし、URLリストをjsonファイルとして保存する
複数の山と渓谷の画像zipを一括uploadする
one commandで実行できるよう作ってある
code:main.ts
import { uploadBulk } from "../複数の画像ファイルをGyazoにuploadするscript/upload.ts";
import {
basename,
extname,
resolve,
// directory内の全てのzipを読み込む
const dir = resolve(Deno.cwd(), Deno.args0); console.log(dir);
const name = basename(dir);
if (!(await Deno.stat(dir)).isDirectory) {
throw Error("${name}" is not a directory. Specify a directory path.);
}
for await (const { name: fileName } of Deno.readDir(dir)) {
const path = resolve(dir, fileName);
if (extname(path) !== ".zip") continue;
const zip = await readZip(path);
console.log(Open ${fileName});
const files: File[] = [];
for (const file of zip) {
const blob = await file.async("blob");
files.push(new File(blob, file.name, { lastModified: file.date.getTime(),
}));
console.log(Extract ${file.name});
}
files.sort((a, b) => parseInt(a.name) - parseInt(b.name));
const year, date = fileName.match(/(\d{4})-(\d{2})/)?.slice?.(1) ?? ""; const title = 『山と渓谷 ${parseInt(year)}年${parseInt(date)}月号』;
console.log(Upload ${title});
const errors = [] as number[];
let counter = 0;
const URLs = [] as string[];
for await (const result of uploadBulk(
files,
{
title,
noIndex: true,
},
)) {
counter++;
if (!result.success) {
if (!(result.reason instanceof Error)) throw result.reason;
console.error([${counter}/${files.length}] , result.reason);
errors.push(counter);
} else {
const { permalink_url, name, index } = result.value;
URLsindex = permalink_url; console.log([${counter}/${files.length}] ${name} ${permalink_url});
}
}
if (errors.length > 0) console.log(errors);
// .zipを削ってファイル名を組み立てる
await Deno.writeTextFile(resolve(dir, ./${fileName.slice(0, -extname(fileName).length)}-gyazo.json), JSON.stringify(URLs));
}